package body Poste_Fixe is

   task body Services is
      monNumero : Integer := 0;
      monEtat : ETAT_POSTE := DECONNECTE;
      monStandard : Integer := -1;

        retour : Integer := 0 ;
        tampon : String := "";
        sock : Sockets.Socket_FD;
        port : Positive := 99999;
        host : String := "localhost";
    begin
        loop
            select
            accept initialiser(num : in Integer; s : in Integer) do
               begin
                    afficherMessage(num,monEtat,"Initialisation");
                    monNumero := num;
		    monStandard := s;
               -- Connexion aupres du standard

                  retour := connecter(monStandard,monNumero); -- # PRAGMA #

                    if (retour = -1) then
                        afficherMessage(monNumero,monEtat,"Echec de connexion au reseau");
                    else
                        monEtat := PRET;
                        afficherMessage(monNumero,monEtat,"Connecte au reseau");
                  end if;
               exception
                  when others => afficherMessage(monNumero,monEtat,"!!! Pragma Exception - connecter !!!");
                     	requeue stop;
               end;
            end;

            or
            	accept appeler(n : in Integer) do
               	    --begin

                    afficherMessage(monNumero,monEtat,"Appeler un poste");
                    if (monEtat = PRET) then
                        afficherMessage(monNumero,monEtat,"Etablissement de la communication");

                        -- demander une communication au standard
                        begin
                     	demanderCommunication(monStandard,monNumero,host,port); -- # PRAGMA #
                        put("ADA >> ");
                        put(monNumero);
                        put(" : Parametre de connexion utilises - host : ");
                        put(host);
                        put(" - port : ");
                        put_line(port);
                        if (port /= 99999) then
                        begin
                                --communication simplifiee a ameliorer
                                Socket(sock);
                                Connect(sock,host,port);
                                Put(sock,"Allo");
                                tampon := Get(sock);
                                afficherCommunication(monNumero,n,tampon);
                                Put(sock,"Au revoir");
                                Shutdown(sock);
                            Exception
                                when Connection_Refused => afficherMessage(monNumero,monEtat,"!!! EXCEPTION : communication refusee !!!");
                                when Socket_Error => afficherMessage(monNumero,monEtat,"!!! EXCEPTION : erreur socket !!!");
                            end;
                        else
                            afficherMessage(monNumero,monEtat,"Impossible d'etablir la communication. Port incorrect");
                        end if;
                    	exception
                  		when others => afficherMessage(monNumero,monEtat,"!!! Pragma Exception - demanderCommunication !!!");
	                end;
                    else
                        if (monEtat = OCCUPE) then
                            afficherMessage(monNumero,monEtat,"Impossible d'appeler. Poste deja en communication");
                        else
                            afficherMessage(monNumero,monEtat,"Impossible d'appeler. Poste non connecte");
                        end if;
                    end if;
--                      exception
--                    	when others => afficherMessage(monNumero,monEtat,"!!! Pragma Exception - demanderCommunication !!!");
--                      end;
                end;
            or
                accept recevoirAppel(host : in String; portSocket : in Positive; appelant : Integer; acceptation : out Boolean) do
                    if (monEtat = PRET) then
                        afficherMessage(monNumero,monEtat,"reception d'un appel");
                        -- Mettre en place une socket en mode serveur => eventuellement prevoir un timeout
                        Socket(sock);
                        Bind(sock,portSocket,host);
                        Listen(sock,1);

                        acceptation := true;
                    else
                        acceptation := false;
                    end if;
                end;
            or
                accept consulterRepondeur do
            		afficherMessage(monNumero,monEtat,"Consultation du repondeur");
                end;
            or
                accept stop do
	               --Deconnexion aupres du standard (PRAGMA)
               		begin
        	          	deconnecter(monStandard,monNumero);
	               	exception
				when others => afficherMessage(monNumero,monEtat,"!!! Pragma Exception - deconnecter !!!");
        		end;
                end;
            end select;
        end loop;
    Exception
	when others => afficherMessage(monNumero,monEtat,"EXCEPTION tache poste !");
    end Services;

    procedure allumer(p : in out Ptr_Poste; n : in Integer; std : in Integer) is
    begin
        p.monNumero := n;
        p.monStandard := std;
        p.mesServices.initialiser(n,std);
    end allumer;

    procedure eteindre(p : in out Ptr_Poste) is
    begin
        p.mesServices.stop;
   end eteindre;

   procedure transmettreAppel(appele : in Integer; host : in String; portSocket : in Positive; appelant : in Integer) is --return Integer is
      acceptation : boolean ;
      unPoste : Poste;
   begin
      unPoste.mesServices.recevoirAppel("localhost",22,1234,acceptation);
      if (not acceptation) then
         null;
         --return -1 ;
      end if;
      --return 0;
   exception
         when others => put_line("ADA >> Pragma Exception - transmettreAppel");
   end;

    procedure afficherMessage(n : in Integer; e : in ETAT_POSTE ; mess : in String) is
    begin
      	put("ADA >>");
      	Int_Io.put(n, Int_Io.Default_Width, Int_Io.Default_Base);
        put(" (");
        case e is
            when OCCUPE => put("occupe");
            when PRET => put("pret");
            when DECONNECTE => put("deconnecte");
        end case;
        put(")");
        put(" : ");
        put_line(mess);
    end afficherMessage;

    procedure afficherCommunication(appelant : in Integer; appele : in Integer; mess : String) is
   begin
      	put("ADA >>");
        Int_Io.put(appelant, Int_Io.Default_Width, Int_Io.Default_Base);
        put(" - [");
        Int_Io.put(appele, Int_Io.Default_Width, Int_Io.Default_Base);
        put("] dit : ");
        put_line(mess);
    end afficherCommunication;

begin
    null;
    Exception
        when others => put_line("!!! EXCEPTION paquetage POSTE !!!");
end Poste_Fixe;
